package org.despair2D.utils 
{
	import flash.events.IOErrorEvent;
	import flash.media.Sound;
	import org.despair2D.debug.Logger;
	import org.despair2D.utils.core.SoundManagerBase;
	import org.despair2D.utils.core.SoundProp;
	
	import org.despair2D.core.ns_despair;
	use namespace ns_despair;
	
	
	/**
	 * @usage
	 * 
	 * [property]
	 * 			1. numSfx
	 * 			2. enabled
	 * 
	 * [method]
	 * 			1. stopSfx
	 * 			2. stopAll
	 */
public class SfxManager extends SoundManagerBase
{
	
	
	private static var m_instance:SfxManager
	public static function getInstance() : SfxManager
	{
		return m_instance ||= new SfxManager()
	}
	
	
	
	/**
	 * 当前正在播放音效数量
	 */
	final public function get numSfx() : int
	{
		return m_numProps
	}
	
	
	/**
	 * 是否开启音效
	 */
	final public function get enabled() : Boolean
	{
		return m_enabled
	}
	
	final public function set enabled( b:Boolean ) : void
	{
		if (m_enabled == b)
		{
			return
		}
		
		m_enabled = b
		
		if (!m_enabled)
		{
			while (m_numProps)
			{
				m_propList[0].forceRecycle()
			}
			
			Logger.reportMessage(this, '禁用音效 !!')
		}
		
		else
		{
			Logger.reportMessage(this, '开启音效 !!')
		}
	}
	
	
	
	
	/**
	 * 停止指定音效
	 * @param	sid
	 */
	final public function stopSfx( sid:uint ) : void
	{
		var prop:SoundProp
		var l:int = m_numProps
		
		while (--l > -1)
		{
			prop = m_propList[l]
			
			if (prop.m_sid == sid)
			{
				prop.forceRecycle()
				return
			}
		}
		
		Logger.reportWarning(this, 'stopSfx', '不存在的sid: (' + sid + ')')
	}
	
	
	/**
	 * 停止全部
	 */
	final public function stopAll() : void
	{
		while (m_numProps)
		{
			m_propList[0].forceRecycle()
		}
		
		Logger.reportMessage(this, '停止全部.')
	}
	
	
	
	
	override public function play( soundRef:*, loops:int = 1, volume:Number = 1, cached:Boolean = true ) : uint
	{
		if (!m_enabled)
		{
			return 0
		}
		
		return super.play(soundRef, loops, volume, cached)
	}
	
	
	override public function loadAndPlay( url:String, loops:int = 1, volume:Number = 1, cached:Boolean = true ) : uint
	{
		if (!m_enabled)
		{
			return 0
		}
		
		return super.loadAndPlay(url, loops, volume, cached)
	}
	

	
	final override ns_despair function removeSoundProp( prop:SoundProp, forced:Boolean ) : void
	{
		var index:int
		
		if(m_numProps > 1)
		{
			index              =  m_propList.indexOf(prop)
			m_propList[index]  =  m_propList[--m_numProps]
			m_propList.pop()
		}
		
		else if (m_numProps == 1)
		{
			m_propList.pop()
			--m_numProps
		}
		
		else
		{
			Logger.reportError(this, 'removeSoundProp', '音乐未知错误.');
		}
	}
	

	final override protected function _playSound( sound:Sound, loops:int, volume:Number, key:String ) : uint
	{
		var prop:SoundProp        =  SoundProp.getSoundProp(sound, loops, volume, key, this)
		m_propList[m_numProps++]  =  prop
		
		return prop.m_sid
	}
	

	final override protected function _modifyVolume() : void
	{
		var l:int = m_numProps
		
		while (--l > -1)
		{
			m_propList[l].setVolume(m_totalVolume)
		}
	}
	
	
	override protected function ____ioError( e:IOErrorEvent ) : void
	{
		super.____ioError(e)
		
		var sound:Sound = e.target as Sound
		var prop:SoundProp
		var l:int = m_numProps
		
		while (--l > -1)
		{
			prop = m_propList[l]
			if (prop.m_sound == sound)
			{
				prop.forceRecycle()
			}
		}
	}
	
	
	
	ns_despair static var m_propList:Vector.<SoundProp> = new Vector.<SoundProp>()
	
	ns_despair static var m_numProps:int
	
	ns_despair var m_enabled:Boolean = true

}

}